package inspection

import (
	"fmt"
	"db2s/global"
	"db2s/outPut"
	"reflect"
	"runtime"
)

type XlsResult struct {
	XlsFileName        string
	XlsSheetNameGather []string
	XlsTatilGather     map[string]string
	XlsSafetySwitch    bool
}
type ResultGeneral struct {
	LogSeq   int64
	event    string
	Type     string
	SaveFile outPut.Result
	Xls      XlsResult
}

func (rg *ResultGeneral) initXlsFile() bool {
	xlsFine := outPut.FileOut("xls", map[string]any{"fileName": rg.Xls.XlsFileName,
		"sheetGather": rg.Xls.XlsSheetNameGather,
		"tailGather":  rg.Xls.XlsTatilGather,
		"safety":      rg.Xls.XlsSafetySwitch,
	})
	if result, err1 := xlsFine.CreateFile(); err1 != nil || !result {
		//err = errors.New(fmt.Sprintf("(%v) %s xls file create fail. xls filename is {%v},case is %v", rg.LogSeq, event, rg.Cell.XlsFileName, err1))
		return false
	}
	rg.SaveFile = xlsFine
	return true
}

func (rg *ResultGeneral) InitResultSaveFile(f string) (b bool) {
	var m = map[string]reflect.Value{
		"xls": reflect.ValueOf(rg.initXlsFile),
	}
	if v, ok := m[f]; ok {
		if v.Kind() == reflect.Func {
			l := v.Call(nil)
			for i := 0; i < len(l); i++ {
				b = l[i].Interface().(bool)
			}
		}
	}
	return
}
func (rg ResultGeneral) isMapOfStringAny(value interface{}) bool {
	valueType := reflect.TypeOf(value)

	if valueType.Kind() != reflect.Map {
		return false
	}
	keyType := valueType.Key()
	elemType := valueType.Elem()

	if keyType.Kind() != reflect.String || elemType.Kind() != reflect.Interface {
		return false
	}
	return true
}
func (rg ResultGeneral) xlsAsyncWrite(m any) bool {
	var (
		ff        string
		sheetName string
		event     = "[xlsAsyncWrite]"
		vlog      string
	)
	pc, _, _, _ := runtime.Caller(1)
	callingFunc := runtime.FuncForPC(pc)
	callFile, callLine := callingFunc.FileLine(pc)
	callFunc := callingFunc.Name()
	callFuncInfo := fmt.Sprintf("Call functions %v Call File %v:%v", callFunc, callFile, callLine)
	vlog = fmt.Sprintf("(%d) %v %v Start asynchronous writing of xls", rg.LogSeq, callFuncInfo, event)
	global.Wlog.Debug(vlog)
	if rg.isMapOfStringAny(m) {
		if v, ok := m.(map[string]any)["sheet"]; ok {
			sheetName = fmt.Sprintf("%v", v)
		}
		if v, ok := m.(map[string]any)["data"]; ok {
			ff = fmt.Sprintf("%v", v)
		}
	}
	if !rg.SaveFile.AppendWrite(sheetName, ff) {
		global.Wlog.Error(fmt.Sprintf("(%d) %s %s xls rows data write fail. xls rows data is {%v}", rg.LogSeq, callFuncInfo, rg.event, ff))
		return false
	}
	return true
}
func (rg ResultGeneral) ResultAsynchronousWriteFile(f any) (b bool) {
	var m = map[string]reflect.Value{
		"xls": reflect.ValueOf(rg.xlsAsyncWrite),
	}
	if v, ok := m[rg.Type]; ok {
		if v.Kind() == reflect.Func {
			value := []reflect.Value{
				reflect.ValueOf(f),
			}
			l := v.Call(value)
			for i := 0; i < len(l); i++ {
				b = l[i].Interface().(bool)
			}
		}
	}
	return
}
func (rg ResultGeneral) Close() (err error) {
	return rg.SaveFile.Close()
}
